<?php
/**
 * Description of SQMCDimClass
 *
 * Sub Question Image File Check
 *
 * @author Chisheng Lu
 * @copyright DoRISE team, Science Education center, NTNU.
 * @since 2010-03-11
 * @version 1.0
 */
class ImgFileChk {
    private $max_width;
    private $max_height;
    private $rsStrImagePic = null;
    private $rsDestImagePic = null;

    function __construct() {
        ini_set('memory_limit', '500M');
        $this->max_width = 500;
        $this->max_height = 500;
    }

    /**
     *
     * @param String $strSrcFileName 原始圖檔案路徑與檔名
     * @param String $strDestFileName
     * @param String $strFileType 圖檔型別
     * @return Boolean
     */
    public function ImageChk($strSrcFileName, $strDestFileName, $strFileType) {
        $bolRtn = false;
        try {
            $this->rsStrImagePic = $this->getImage($strSrcFileName, $strFileType);
        } catch (Exception $e) {
            throw new Exception($e);
        }
        //取得圖片的原始寬度、高度
        $aryImgSize = getimagesize($strSrcFileName);
        if (!$aryImgSize) {
            throw new Exception('讀取圖檔長寬點數錯誤！');
        }
        list($width,$height) = $aryImgSize;

        $x_ratio = $this->max_width / $width;
        $y_ratio = $this->max_height / $height;

        if ( ($width <= $this->max_width) && ($height <= $this->max_height) ) {
            $tn_width = $width;
            $tn_height = $height;
        } elseif (($x_ratio * $height) < $this->max_height) {
            $tn_height = ceil($x_ratio * $height);
            $tn_width = $this->max_width;
        }else {
            $tn_width = ceil($y_ratio * $width);
            $tn_height = $this->max_height;
        }

        //在記憶體中建立新圖
        $this->rsDestImagePic = imagecreatetruecolor($tn_width,$tn_height);
        if (!$this->rsDestImagePic) {
            throw new Exception('建立新圖錯誤！');
        }
        //將原始圖片複製並縮小成為新的圖片
        $bolRtn = imagecopyresampled($this->rsDestImagePic,$this->rsStrImagePic,0,0,0,0,$tn_width, $tn_height,$width,$height);
        if (!$bolRtn) {
            throw new Exception('複製成新圖錯誤！');
        }
        //將新圖重新寫入目標路徑
        //imagejpeg($this->rsDestImagePic,$strDestFileName,100);
        try {
            $bolRtn = $this->setImage($this->rsDestImagePic,$strDestFileName,$strFileType);
        } catch (Exception $e) {
            throw new Exception($e);
        }

        return $bolRtn;

    }

    /**
     *
     * @param Resource $rsDestImagePic
     * @param String $strDestFileName
     * @param String $strFileType
     * @return Boolean
     */
    private function setImage($rsDestImagePic, $strDestFileName, $strFileType) {
        switch ($strFileType) {
            case 'image/pjpeg':
            case 'image/jpeg':
                $bolRtn = imagejpeg($rsDestImagePic, $strDestFileName, 100);
                break;
            case 'image/gif':
                $bolRtn = imagegif($rsDestImagePic, $strDestFileName, 100);
                break;
            case 'image/x-png':
            case 'image/png':
                $bolRtn = imagepng($rsDestImagePic, $strDestFileName);
                break;
            case 'image/bmp':
                $bolRtn = image2wbmp($rsDestImagePic, $strDestFileName);
                break;
            default:
                throw new Exception('圖檔類行不支援！');
                break;
        }
        if (!$bolRtn) {
            throw new Exception('儲存圖檔 ' + $strDestFileName + '.' . $strFileType . '  錯誤！');
        }
        return $bolRtn;
    }

    /**
     *
     * @param String $strFileName
     * @param String $strFileType
     * @return Object 記憶體裡的圖檔
     * @abstract 依照不同檔案型別，將原始圖片載入記憶體
     */
    private function getImage($strFileName, $strFileType) {
        switch ($strFileType) {
            case 'image/pjpeg';
            case 'image/jpeg':
                $rsImagePic = imagecreatefromjpeg($strFileName);
                break;
            case 'image/gif':
                $rsImagePic = imagecreatefromgif($strFileName);
                break;
            case 'image/x-png':
            case 'image/png':
                $rsImagePic = imagecreatefrompng($strFileName);
                break;
            case 'image/bmp':
                $rsImagePic = $this->imagecreatefrombmp($strFileName);
                break;
            default:
                throw new Exception($strFileType . '圖檔類行不支援！');
                break;
        }
        if (!$rsImagePic) {
            throw new Exception('讀取圖檔 ' + $strFileName + '.' . $strFileType . '  錯誤！');
        }
        return $rsImagePic;
    }

    /**
     *
     * @param String $filename
     * @return Image
     */
    private function imagecreatefrombmp( $filename ) {
        $file = fopen( $filename, "rb" );
        $read = fread( $file, 10 );
        while( !feof( $file ) && $read != "" ) {
            $read .= fread( $file, 1024 );
        }
        $temp = unpack( "H*", $read );
        $hex = $temp[1];
        $header = substr( $hex, 0, 104 );
        $body = str_split( substr( $hex, 108 ), 6 );
        if( substr( $header, 0, 4 ) == "424d" ) {
            $header = substr( $header, 4 );
            // Remove some stuff?
            $header = substr( $header, 32 );
            // Get the width
            $width = hexdec( substr( $header, 0, 2 ) );
            // Remove some stuff?
            $header = substr( $header, 8 );
            // Get the height
            $height = hexdec( substr( $header, 0, 2 ) );
            unset( $header );
        }
        $x = 0;
        $y = 1;
        $image = imagecreatetruecolor( $width, $height );
        if (!$image) {
            throw new Exception('建立新圖錯誤！');
        }
        foreach( $body as $rgb ) {
            $r = hexdec( substr( $rgb, 4, 2 ) );
            $g = hexdec( substr( $rgb, 2, 2 ) );
            $b = hexdec( substr( $rgb, 0, 2 ) );
            $color = imagecolorallocate( $image, $r, $g, $b );
            if (!$color) {
                throw new Exception('分派圖色彩錯誤！');
            }
            $bolRtn = imagesetpixel( $image, $x, $height-$y, $color );
            if (!$bolRtn) {
                throw new Exception('畫一圖點錯誤！');
            }
            $x++;
            if( $x >= $width ) {
                $x = 0;
                $y++;
            }
        }
        return $image;
    }

    function  __destruct() {
        if ($this->rsStrImagePic != null) {
            imagedestroy($this->rsStrImagePic);
        }
        if ($this->rsDestImagePic != null) {
            imagedestroy($this->rsDestImagePic);
        }
    }
}
?>
